#include <set>
#include <utility>
#include <iostream>


using std::cout;
using std::endl;
using std::set;
using std::string;
using std::pair;

int test0()
{
    //set 不是一个完整的类型
    //set<int>  加上尖括号以及类型之后，才是一个完整的类型
    cout <<"sizeof(set<int>):" << sizeof(set<int>) << endl;
    int arr[10] = {4, 3, 2, 3, 3, 4, 1, 2, 3, 5};

    //set<int> numbers;//没有元素
    set<int> numbers(arr, arr + 10);
    cout << "numbers'size:" << numbers.size() << endl;
    cout << "numbers' empty:" << numbers.empty() << endl;
    //set的遍历
    set<int>::iterator it = numbers.begin();
    for(; it != numbers.end(); ++it) {
        cout << *it << " ";
    }
    cout << endl;

    for(auto & e : numbers) {
        cout << e << " ";
    }
    cout << endl;

    //set的特点：
    //1. 内部不能存放关键字相同的元素
    //2. 默认情况下按升序的方式进行排列
    //3. 底层实现采用了红黑树(rbTree)
    //a. 节点不是红色的就是黑色的
    //b.根节点是黑色
    //c.叶子节点是黑色
    //d.不能有连续的两个节点是红色
    //e.从根节点到任意一个叶子节点上的黑色节点数目相同
    //4.查找/添加/删除元素时，其时间复杂度为O(logN) ,即二分查找
    
    //通过迭代器是否可以修改其中的元素:不可以
    it = numbers.begin();
    cout << "*it:" << *it << endl;
    //*it = 2;//error, 如果能直接修改，会导致元素相同或者不再有序

    return 0;
}

void test1()
{
    set<int> numbers{4, 3, 2, 3, 2, 1, 3, 5};
    for(auto & e : numbers) {
        cout << e << " ";
    }
    cout << endl;

    //查找元素
    int cnt = numbers.count(1);
    cout << "cnt:" << cnt << endl;//1
    cnt = numbers.count(10);
    cout << "cnt:" << cnt << endl;//0
                                
    //iterator是一个嵌套类
    set<int>::iterator it = numbers.begin();
    /* it = numbers.find(2); */
    it = numbers.find(10);
    if(it == numbers.end()) {
        cout << "没有找到" << endl;
    } else {
        cout << "找到了" << *it << endl;
    }

    //添加新的元素
    //返回的一对pair中的second表示这一次的插入是否成功
    //如果成功，返回为true；如果失败，返回为false
    //pair中的first代表的是在set中的位置信息
    pair<set<int>::iterator, bool> ret = numbers.insert(6);
    if(ret.second == true) {
        cout << "添加成功" << *ret.first << endl; 
    } else {
        cout << "添加失败，元素已经在set中了" << endl;
        cout << *ret.first << endl;
    }

    //删除元素
    numbers.erase(6);
    cout << "cnt:" << numbers.count(6) << endl;

    //set不能使用下标访问运算符
    //cout << numbers[0] << endl;//error
}

void test2()
{
    std::pair<int, string> city{1, "武汉"};
    cout << city.first << " --> " << city.second << endl;

}



int main()
{
    /* test0(); */
    test1();
    test2();
    return 0;
}
